package com.fhx.core.utils

import android.annotation.SuppressLint
import android.app.Activity
import android.content.Context
import android.content.Intent
import android.content.pm.PackageManager
import android.net.Uri
import android.net.wifi.WifiInfo
import android.net.wifi.WifiManager
import android.os.Build
import android.provider.Settings
import android.telephony.TelephonyManager
import android.text.TextUtils
import android.util.Log
import androidx.core.content.FileProvider
import com.fhx.core.AppContext
import java.io.BufferedReader
import java.io.File
import java.io.FileReader
import java.io.IOException
import java.net.NetworkInterface
import java.util.*

object SystemUtil {
    /**
     * 跳转到设置-允许安装未知来源-页面
     */
    fun startInstallPermissionSettingActivity(
        activity: Activity,
        requestCode: Int
    ) {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O && activity.applicationInfo.targetSdkVersion >= Build.VERSION_CODES.O) {
            //注意这个是8.0新API
            try {
                val hasInstallPermission =
                    activity.packageManager.canRequestPackageInstalls()
                if (!hasInstallPermission) {
                    val packageURI =
                        Uri.parse("package:" + activity.packageName)
                    val intent =
                        Intent(Settings.ACTION_MANAGE_UNKNOWN_APP_SOURCES, packageURI)
                    activity.startActivityForResult(intent, requestCode)
                }
            } catch (e: Exception) {
            }
        }
    }

    /**
     * 安装应用
     */
    fun installApk(path:String){
        val file = File(path)
        val intent = Intent()
        intent.flags = Intent.FLAG_ACTIVITY_NEW_TASK
        intent.action = Intent.ACTION_VIEW
        val context: Context = AppContext.instance
        var uri: Uri? = null
        uri = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
            intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION)
            FileProvider.getUriForFile(
                context,
                context.packageName + ".fileprovider", file
            )
        } else {
            Uri.fromFile(file)
        }
        intent.setDataAndType(uri, "application/vnd.android.package-archive")
        context.startActivity(intent)
    }

    /**
     * 获取设备的唯一标识
     * 优先顺序imei->wifi地址->生成UUID
     * @param context
     * @return 唯一标识字符串
     */
    fun getDeviceUUID(context: Context): String {
        var uuid: String? = SharePreferencesUtil.getString(context,"DeviceUUID")
        if (TextUtils.isEmpty(uuid)) {
            uuid = getIMEI(context)
            if (TextUtils.isEmpty(uuid)) {
                uuid = getWifiMac(context)
            }
            if (TextUtils.isEmpty(uuid)) {
                //这个在10.0手机上也可以获取，但是有些厂商的获取出来的为null
                uuid = Settings.System.getString(
                    context.contentResolver,
                    Settings.System.ANDROID_ID
                )
            }
            if(TextUtils.isEmpty(uuid)){
                uuid = getFixedUUID()
            }
            if (TextUtils.isEmpty(uuid)) {
                uuid = UUID.randomUUID().toString()
            }
            SharePreferencesUtil.saveString(context,"DeviceUUID", uuid!!)
        }
        return uuid!!
    }

    /**
     * 获取IMEI
     */
    @SuppressLint("MissingPermission")
    fun getIMEI(context: Context): String? {
        if(Build.VERSION.SDK_INT<Build.VERSION_CODES.Q) {
            val telMgr = context.applicationContext
                .getSystemService(Context.TELEPHONY_SERVICE) as TelephonyManager
            try {
                //调用这个方法，如果没申请READ_EXTERNAL_STORAGE权限，在6.0以上手机都会抛异常
                // 如果申请了READ_EXTERNAL_STORAGE权限，在10.0以前的手机上是正常的，
                // 在10.0及以后的手机上，如果targetSdkVersion小于10.0（29）会返回null，如果targetSdkVersion>=29，则会抛异常
                return telMgr.deviceId
            } catch (e: Exception) {
                e.printStackTrace()
            }
        }
        return null
    }

    /**
     * 获取wifi地址，多版本兼容
     */
    fun getWifiMac(context: Context): String?{
        var mac: String? = ""
        if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) {
            mac = getMacDefault(context)
        } else if (Build.VERSION.SDK_INT == Build.VERSION_CODES.M) {
            mac = getMacAddress()
        } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
            mac = getMacFromHardware()
        }
        return mac
    }

    /**
     * Android 6.0 之前（不包括6.0）获取mac地址
     * 必须的权限 <uses-permission android:name="android.permission.ACCESS_WIFI_STATE"></uses-permission>
     * @param context * @return
     */
    @SuppressLint("MissingPermission")
    private fun getMacDefault(context: Context?): String? {
        var mac = ""
        if (context == null) {
            return mac
        }
        val wifi =
            context.getSystemService(Context.WIFI_SERVICE) as WifiManager
        var info: WifiInfo? = null
        try {
            info = wifi.connectionInfo
        } catch (e: Exception) {
            e.printStackTrace()
        }
        if (info == null) {
            return null
        }
        mac = info.macAddress
        if (!TextUtils.isEmpty(mac)) {
            mac = mac.toUpperCase(Locale.ENGLISH)
        }
        return mac
    }

    /**
     * Android 6.0-Android 7.0 获取mac地址
     */
    fun getMacAddress(): String? {
        var wifiAddress: String? = null
        try {
            wifiAddress =
                BufferedReader(FileReader(File("/sys/class/net/wlan0/address")))
                    .readLine()
        } catch (e: IOException) {
            e.printStackTrace()
        }
        return wifiAddress
    }

    /**
     * Android 7.0之后获取Mac地址
     * 遍历循环所有的网络接口，找到接口是 wlan0
     * 必须的权限 <uses-permission android:name="android.permission.INTERNET"></uses-permission>
     * @return
     */
    fun getMacFromHardware(): String? {
        try {
            val all =
                Collections.list(NetworkInterface.getNetworkInterfaces())
            for (nif in all) {
                if (!nif.name.equals("wlan0", ignoreCase = true)) continue
                val macBytes = nif.hardwareAddress ?: return ""
                val res1 = StringBuilder()
                for (b in macBytes) {
                    res1.append(String.format("%02X:", b))
                }
                if (!TextUtils.isEmpty(res1)) {
                    res1.deleteCharAt(res1.length - 1)
                }
                return res1.toString()
            }
        } catch (e: Exception) {
            e.printStackTrace()
        }
        return ""
    }

    @SuppressLint("MissingPermission")
    //根据手机硬件信息生成uuid
    fun getFixedUUID(): String? {
        val m_szDevIDShort = "20" +
                    Build.BOARD.length % 10 +
                    Build.BRAND.length % 10 +
                    Build.CPU_ABI.length % 10 +
                    Build.DEVICE.length % 10 +
                    Build.DISPLAY.length % 10 +
                    Build.HOST.length % 10 +
                    Build.ID.length % 10 +
                    Build.MANUFACTURER.length % 10 +
                    Build.MODEL.length % 10 +
                    Build.PRODUCT.length % 10 +
                    Build.TAGS.length % 10 +
                    Build.TYPE.length % 10 +
                    Build.USER.length % 10 //13 位

        val serial = if (Build.VERSION.SDK_INT < Build.VERSION_CODES.Q) {
            try {
                if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
                    Build.getSerial()
                    //serial = Build.SERIAL;//这个字段在api 26以后是unknown
                } else {
                    Build.SERIAL
                }
            } catch (exception: java.lang.Exception) {
                //serial需要一个初始化
                "androidSerial" // 随便一个初始化
            }
        } else {
            //10.0以后，都读不到deviceId以及serial
            "androidSerial" // 随便一个初始化
        }
        //使用硬件信息拼凑出来的15位号码
        return UUID(m_szDevIDShort.hashCode().toLong(), serial.hashCode().toLong()).toString()
    }

    /**
     * 获取版本名称
     *
     * @param context
     * @return
     */
    fun getVerName(context: Context): String? {
        var verName: String? = ""
        try {
            verName = context.packageManager.getPackageInfo(
                context.packageName, 0
            ).versionName
        } catch (e: PackageManager.NameNotFoundException) {
            e.message?.let { Log.e("msg", it) }
        }
        return verName
    }

}